package tech.mhuang.pacebox.springboot.autoconfiguration.oss;


import lombok.extern.slf4j.Slf4j;
import org.springframework.boot.autoconfigure.condition.ConditionalOnClass;
import org.springframework.boot.autoconfigure.condition.ConditionalOnMissingBean;
import org.springframework.boot.autoconfigure.condition.ConditionalOnProperty;
import org.springframework.boot.context.properties.EnableConfigurationProperties;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import tech.mhuang.pacebox.oss.BaseOssHandler;
import tech.mhuang.pacebox.oss.OssFieldProperties;
import tech.mhuang.pacebox.oss.OssTemplate;
import tech.mhuang.pacebox.oss.interceptor.OssDeleteInteceptor;
import tech.mhuang.pacebox.oss.interceptor.OssDownloadInterceptor;
import tech.mhuang.pacebox.oss.interceptor.OssUploadInterceptor;
import tech.mhuang.pacebox.sms.SmsOperation;
import tech.mhuang.pacebox.springboot.autoconfiguration.ConfigConsts;

import javax.annotation.PostConstruct;
import java.util.List;
import java.util.Map;
import java.util.Set;

/**
 * oss配置
 *
 * @author mhuang
 * @since 1.1.3
 */
@Configuration
@ConditionalOnClass(SmsOperation.class)
@EnableConfigurationProperties(value = OssProperties.class)
@ConditionalOnProperty(prefix = ConfigConsts.OSS, name = ConfigConsts.ENABLE, havingValue = ConfigConsts.TRUE)
@Slf4j
public class OssAutoConfiguration {

    private final OssProperties properties;

    public OssAutoConfiguration(OssProperties properties) {
        this.properties = properties;
    }

    @Bean
    @ConditionalOnMissingBean
    public OssTemplate ossTemplate() {
        OssTemplate ossTemplate = new OssTemplate();
        configure(ossTemplate);
        return ossTemplate;
    }

    /**
     * 配置OSS模板
     *
     * @param ossTemplate OSS模板
     */
    private void configure(OssTemplate ossTemplate) {
        Map<String, OssFieldProperties> handlerMap = properties.getBeanMap();
        Set<String> keys = handlerMap.keySet();
        for (String key : keys) {
            OssFieldProperties fieldProperties = handlerMap.get(key);
            try {
                BaseOssHandler handler = fieldProperties.getDriver().newInstance();
                handler.setProperties(handlerMap.get(key));
                ossTemplate.addHandler(key, handler);
            } catch (Exception e) {
                log.error("获取OSS处理类失败", e);
            }
        }
    }

    /**
     * OSS模板处理配置
     *
     * @author mhuang
     * @since 1.1.2
     */
    @Configuration
    public static class OssTemplatePostProcessingConfiguration {

        private final OssTemplate ossTemplate;
        private final List<OssUploadInterceptor> ossUploadInterceptorList;
        private final List<OssDownloadInterceptor> ossDownloadInterceptorList;
        private final List<OssDeleteInteceptor> ossDeleteInteceptorList;

        public OssTemplatePostProcessingConfiguration(OssTemplate ossTemplate, List<OssUploadInterceptor> ossUploadInterceptorList, List<OssDownloadInterceptor> ossDownloadInterceptorList, List<OssDeleteInteceptor> ossDeleteInteceptorList) {
            this.ossTemplate = ossTemplate;
            this.ossUploadInterceptorList = ossUploadInterceptorList;
            this.ossDownloadInterceptorList = ossDownloadInterceptorList;
            this.ossDeleteInteceptorList = ossDeleteInteceptorList;
        }


        /**
         * 添加拦截器
         */
        @PostConstruct
        public void init() {
            ossTemplate.setUploadInterceptors(ossUploadInterceptorList);
            ossTemplate.setDownloadInterceptors(ossDownloadInterceptorList);
            ossTemplate.setDeleteInteceptors(ossDeleteInteceptorList);
        }
    }
}
